package server

import (
	"go.uber.org/zap"
	"me/123/common/dao/mysql"
	"me/123/common/dao/redis"
	"me/123/common/global"
	"me/123/common/model"
	"me/123/common/proto/product"
	"time"
)

func ProductList(req *product.ProductListRequest) (*product.ProductListResponse, error) {
	query := global.DB.Model(&model.EbStoreProduct{})
	if req.Keyword != "" {
		_, err := mysql.KeywordQuery(req.Keyword, query)
		if err != nil {
			zap.S().Error("mysql.KeywordQuery failed", zap.Error(err))
			return nil, err
		}
	}
	if req.IsNew != 0 {
		oneMonthAgo := time.Now().AddDate(0, -1, 0)
		_, err := mysql.IsNewQuery(oneMonthAgo, query)
		if err != nil {
			zap.S().Error("mysql.IsNewQuery failed", zap.Error(err))
			return nil, err
		}
	}
	if req.PriceMin > 0 {
		query = query.Where("price >= ?", req.PriceMin)
	}
	if req.PriceMax > 0 {
		query = query.Where("price <= ?", req.PriceMax)
	}
	if req.IsHot > 0 {
		query = query.Where("is_hot = ?", req.IsHot)
	}
	if req.TopCategory > 0 {
		categoryLevel, err := mysql.Scan(req.TopCategory)
		if err != nil {
			zap.S().Error("products list scan error", zap.Error(err))
			return nil, err
		}
		if categoryLevel == 0 {
			subCategoryIDs, err := mysql.Pluck(req.TopCategory)
			if err != nil {
				zap.S().Error("products list pluck error", zap.Error(err))
				return nil, err
			}
			_, err = mysql.ProductCateList(subCategoryIDs, query)
			if err != nil {
				zap.S().Error("products cate list error", zap.Error(err))
				return nil, err
			}
		} else {
			query = query.Where("cate_id = ?", req.TopCategory)
		}
	}
	page := req.Pages
	if page <= 0 {
		page = 1
	}
	pageSize := req.PagePerNums
	switch {
	case pageSize > 100:
		pageSize = 100
	case pageSize <= 0:
		pageSize = 10
	}
	offset := (page - 1) * pageSize
	list, err := mysql.ProductList(query, offset, pageSize)
	if err != nil {
		zap.S().Error("products list error", zap.Error(err))
		return nil, err
	}
	var productItem []*product.ProductListItem
	for _, item := range list {
		productItem = append(productItem, &product.ProductListItem{
			Id:        int64(item.Id),
			CateId:    int64(item.CateId),
			StoreName: item.StoreName,
			Browse:    int64(item.Browse),
			Sales:     int64(item.Sales),
			Collect:   int64(item.Collect),
			StoreInfo: item.StoreInfo,
			Image:     item.Image,
			Price:     float32(item.Price),
		})
	}
	var total int64
	query.Count(&total)
	return &product.ProductListResponse{
		Total: total,
		List:  productItem,
	}, nil
}

func List(req *product.ListRequest) (*product.ListResponse, error) {
	query := global.DB.Model(&model.EbStoreProduct{})

	if req.IsHot != 0 {
		query = query.Where("is_hot = ?", req.IsHot)
	}
	if req.IsBest != 0 {
		query = query.Where("is_best = ?", req.IsBest)
	}
	if req.IsPostage != 0 {
		query = query.Where("is_postage = ?", req.IsPostage)
	}

	list, err := redis.GetList(query)
	if err != nil {
		return nil, err
	}

	var item []*product.ProductListItem

	for _, storeProduct := range list {
		item = append(item, &product.ProductListItem{
			Id:        int64(storeProduct.Id),
			CateId:    int64(storeProduct.CateId),
			StoreName: storeProduct.StoreName,
			Browse:    int64(storeProduct.Browse),
			Sales:     int64(storeProduct.Sales),
			Collect:   int64(storeProduct.Collect),
			StoreInfo: storeProduct.StoreInfo,
			Image:     storeProduct.Image,
			Price:     float32(storeProduct.OtPrice),
		})
	}

	response := &product.ListResponse{
		List: item,
	}

	return response, nil
}

func UserList(req *product.UserListRequest) (*product.UserListResponse, error) {

	Recommended, err := mysql.QueryUserRecommended(req.UserId)
	if err != nil {
		return nil, err
	}

	var item []*product.ProductListItem
	for _, storeProduct := range Recommended {
		item = append(item, &product.ProductListItem{
			Id:        int64(storeProduct.Id),
			CateId:    int64(storeProduct.CateId),
			StoreName: storeProduct.StoreName,
			Browse:    int64(storeProduct.Browse),
			Sales:     int64(storeProduct.Sales),
			Collect:   int64(storeProduct.Collect),
			StoreInfo: storeProduct.StoreInfo,
			Image:     storeProduct.Image,
			Price:     float32(storeProduct.Price),
		})
	}

	return &product.UserListResponse{List: item}, nil
}
